<?php
class Location {
	/**
	* @var mixed Mysql connection
	*/
	var $mysqli = null;
	/**
	* @var array User credentials (id, email, type)
	*/
	var $user = null;
	/**
	* @var array Notifications
	*/
	var $notif = array();
	/**
	* @var string Area of concentration
	*/
	var $area = 'loc';
	/**
	* @var string Database table to be used
	*/
	var $table = 'Locations';
	/**
	* @var mixed Options
	*/
	var $opts = null;
	/**
	* @var string Source of document
	*/
	var $srcid = null;
	
	/**
	* Location constructor
	* Initializes location variables for intended request
	* 
	* @param string $area Area of concentration
	* @param resource $mysqli Current mysql connection
	* @param resource $user User credentials (id, email, type)
	*/
	function __construct($area, $mysqli, $user) {
		# Include all needed classes
		require_once "class/setting.php";
		require_once "class/file.php";
		require_once "class/resource.php";
		require_once "class/microorganism.php";
		require_once "class/image.php";
		require_once "class/document.php";
		require_once "class/section.php";
		require_once "class/project.php";
		require_once "class/tool.php";
		
		$this->mysqli = $mysqli;
		$this->user = $user;
		$this->area = $area;
		
		switch($area) {
			# Microorganisms
			case 'micro':
				$this->table = 'MicroLocs';
			break;
			
			# Projects
			case 'proj':
				$this->table = 'ProjLocs';
			break;
			
			# Resources
			case 'rsrc':
				$this->table = 'LocDocs';
			break;
			
			# Locations
			default:
				$this->table = 'Locations';
			break;
		}
	}
	
	/**
	* Search location
	* Searches for a location based on
	* query string, optional paramaters as constraints,
	* start and end line of result in a mysql resource
	* 
	* @access public
	* @param string $query Keyword/s to look for in the database
	* @param array $opts Contains constraints in search (category, order, author, etc.)
	* @param integer $start Beginning line of searched keyword in mysql resource
	* @param integer $limit End of returned mysql resource as a result of search
	* 
	* @return array Mixed result from mysql query and size of returned rows
	*/
	public function search($query, $opts, $start, $limit) {
		$query = is_array($query) ? $query : Tool::trimout($query);
		$selSize = "SELECT FOUND_ROWS()";
		
		# Search via ID
		if($opts["c"]=="id" or $opts["c"]=="view") {
			$query = empty($opts['id']) ? $query : $opts['id'];
			
			$sel = "
				SELECT SQL_CALC_FOUND_ROWS DISTINCT T1.* FROM Locations AS T1 WHERE T1.ID='{$query}' ".(in_array($this->user['type'], array('ADMIN','PRIME')) ? '' : "AND T1.Remove='0'")."
					AND ('{$this->user['type']}'='PRIME' OR T1.Visib='PUB' OR (T1.Visib='PRV' AND (T1.CrtBy='{$this->user['id']}'
					OR (SELECT COUNT(*) FROM LocCoeds AS T2 WHERE T2.PID='{$query}' AND T2.CID='{$this->user['id']}') > 0)))
				ORDER BY T1.Name
			";
		}
		else {
			$cond = "";
			
			# Other category
			switch($opts["c"]) {
				# Coordinates
				case "proj":
					$categ = "
						INNER JOIN ProjLocs AS T3 INNER JOIN Projects AS T4
							ON T1.ID=T3.CID AND T3.PID=T4.ID
						WHERE T4.ID='{$query}' OR T4.Title LIKE '%{$query}%' OR T4.Abstr LIKE '%{$query}%'
					";
				break;
				
				# Microorganisms
				case "micro":
					$categ = "
						INNER JOIN MicroLocs AS T3 INNER JOIN Microorganisms AS T4
							ON T1.ID=T3.CID AND T3.PID=T4.ID
						WHERE T4.ID='{$query}' OR T4.Name LIKE '%{$query}%' OR T4.Notes LIKE '%{$query}%'
					";
				break;
				
				# Multiple ids
				case "multi-id":
					$categ = "WHERE T1.ID IN ('".implode("','", $query)."')";
				break;
			}
			
			# Ordering
			$opts["ob"] = isset($opts["ob"]) ? $opts["ob"] : "Name";
			$opts["oa"] = isset($opts["oa"]) ? $opts["oa"] : "ASC";
			
			# Include words/phrase
			if(!empty($opts["i"])) {
				$cond .= " (T1.Name LIKE '%{$opts["i"]}%' OR T1.Notes LIKE '%{$opts["i"]}%') AND ";
			}
			
			/* # Exclude words/phrase
			if(!empty($opts["e"])) {
				$exclude = explode(", ", $opts["e"]);
				$name = "T1.Name NOT LIKE '%".implode("%' OR T1.Name NOT LIKE '%", $exclude)."%'";
				$notes = "T1.Notes NOT LIKE '%".implode("%' OR T1.Notes NOT LIKE '%", $exclude)."%'";
				$cond .= " ({$name} AND {$notes}) AND ";
			} */
			
			# Excluded words/phrase
			if(!empty($opts["e"])) {
				$arrQuery = explode(", ", $opts["e"]);
				$cond .= "(T1.Name NOT LIKE '%".implode("%' AND T1.Name NOT LIKE '%", $arrQuery)."%') AND ";
			}
			
			# Creator
			if(!empty($opts["cb"])) {
				if(empty($opts['cbi'])) {
					$name = explode(", ", $opts["cb"]);
					
					# Account name
					if(count($name)==3) {
						list($lname, $fname, $mi) = $name;
						$cond .= " (T1.CrtBy IN (SELECT ID FROM Accounts WHERE Lname='".Tool::trimout($lname)."'AND Fname='".Tool::trimout($fname)."') AND";
					}
					# Email
					else if(strrpos($opts['cb'], '@') > 1) {
						$cond .= " (T1.CrtBy IN (SELECT ID FROM Accounts WHERE Email='{$opts['cb']}')) AND ";
					}
					# Other
					else {
						$cond .= "(T1.CrtBy='%{$query}%') AND ";
					}
				}
				# Account ID
				else {
					$cond .= " (T1.CrtBy='{$opts['cbi']}') AND ";
				}
			}
			
			# Creation date
			if(!empty($opts['co']['s'])) {
				# Date range
				if(!empty($opts["co"]["e"])) {
					$cond .= " (T1.CrtOn BETWEEN '".Tool::trimout($opts["co"]["s"])."' AND '".Tool::trimout($opts["co"]["e"])."') AND ";
				}
				# Exact date
				else {
					$cond .= " (T1.CrtOn='".Tool::trimout($opts["co"]["s"])."') AND ";
				}
			}
			
			# Coordinates
			if(isset($opts['lat']) and isset($opts['lng'])) {
				$cond .= " ((T1.Lat BETWEEN ".(floatval($opts['lat'])-0.5)." AND ".(floatval($opts['lat'])+0.5).") AND ";
				$cond .= " (T1.Lng BETWEEN ".(floatval($opts['lng'])-0.5)." AND ".(floatval($opts['lng'])+0.5).")) AND ";
			}
			
			# Name
			if(empty($opts["c"]) or ($opts["c"]=="name" and !empty($query))) {
				$cond .= " (T1.Name LIKE '%{$query}%') AND ";
			}
			
			# Removed items
			$cond .= (in_array($this->user['type'], array('ADMIN','PRIME')) and $opts['c']=='remove') ? " T1.Remove='1' AND " : " T1.Remove='0' AND ";
			
			# Limit of returned rows
			$range = (isset($start) and !empty($limit)) ? "LIMIT {$start}, {$limit}" : '';
			
			if(empty($categ)) {
				$cond = "
					WHERE {$cond} (T1.Visib='PUB' OR ('{$this->user['type']}'='PRIME')
						OR (T1.Visib='PRV' AND (T1.CrtBy='{$this->user['id']}'
						OR (SELECT COUNT(T2.CID) FROM ImgCoeds AS T2 WHERE T2.PID=T1.ID AND T2.CID='{$this->user['id']}') > 0)))
				";
			}
			else {
				$cond = "
					{$categ} AND {$cond} (T1.Visib='PUB' OR ('{$this->user['type']}'='PRIME')
						OR (T1.Visib='PRV' AND (T1.CrtBy='{$this->user['id']}'
						OR (SELECT COUNT(T2.CID) FROM ImgCoeds AS T2 WHERE T2.PID=T1.ID AND T2.CID='{$this->user['id']}') > 0)))
				";
			}
			
			$sel = "
				SELECT SQL_CALC_FOUND_ROWS DISTINCT T1.* FROM Locations AS T1 {$cond} ORDER BY T1.{$opts["ob"]} {$opts["oa"]} {$range}
			";
		}
		
		# Find in database
		$res = $this->mysqli->query($sel);
		$size = $this->mysqli->query($selSize);
		$size = $size->fetch_row();
		
		# Return results and size of rows
		return array($res, $size[0]);
	}
	
	/**
	* Create location
	* Create a new location
	* 
	* @access public
	* @param mixed $name Name
	* @param integer $lat Latitude
	* @param integer $lng Longitude
	* @param string $gname Gmap name
	* @param integer $glat Gmap latitude
	* @param integer $glng Gmap longitude
	* @param string $notes Notes
	* @param array $micros Microorganisms
	* @param array $files Files
	* @param array $coeds Coeditors
	* @param string $categ Category
	* @param string $visib Visibility
	* 
	* @return mixed ID on success, false on failure
	*/
	public function create(
		$name, $lat, $lng, $gname, $glat, $glng, $notes, $ref, $micros,
		$files, $coeds, $categ, $visib
	) {
		$id = Tool::generateID('loc'); 
		
		# Insert location string
		$ins = "INSERT INTO Locations VALUES (
			'{$id}', '{$categ}', '{$visib}', '".mysql_real_escape_string($name)."', {$lat}, {$lng},
			".(empty($gname) ? "'".$name."'" : "'".mysql_real_escape_string($gname)."'").",
			".(empty($glat) ? $lat : $glat).", ".(empty($glng) ? $lng : $glng).",
			".(empty($notes) ? 'NULL' : mysql_real_escape_string($notes)).",
			".(empty($ref) ? 'NULL' : mysql_real_escape_string($ref)).",
			'".(empty($coeds["val"]) ? 0 : count($coeds["val"]))."',
			NULL, NULL, '0', NULL, NULL, '0', '{$this->user['id']}', '".date('Y-m-d H:i:s:ms')."', '0'
		)";
		
		# Insert into database
		if($this->mysqli->query($ins)) {
			# Append microorganisms
			if(!empty($micros['val'])) {
				$micro = new Microorganism('loc', $this->mysqli, $this->user);
				$micro->append($micros, $id, true);
			}
			
			# Append files
			if(!empty($files['name'])) {
				$file = new File('loc', $this->mysqli, $this->user);
				$file->append($files, $id, $categ, $visib);
			}
			
			# Append coeditors
			if(!empty($coeds['val'])) {
				$edtr = new Editor('loc', $this->mysqli, $this->user);
				$edtr->append($coeds, $id, false);
			}
		}
		# Error in creating location
		else {
			$this->notif = "ERROR: insert location $name - $gname <hr/>";
		}
		
		# Created location successfully
		if(empty($this->notif)) {
			return $id;
		}
		
		# Error occurred
		//echo '<pre>', var_dump($this->notif), '</pre>';
		return false;
	}
	
	/**
	* Update location
	* Update an existing location on the system
	* 
	* @access public
	* @param string $id Location ID
	* @param mixed $name Name
	* @param integer $lat Latitude
	* @param integer $lng Longitude
	* @param string $gname Gmap name
	* @param integer $glat Gmap latitude
	* @param integer $glng Gmap longitude
	* @param string $notes Notes
	* @param array $micros Microorganisms
	* @param array $imgs Images
	* @param array $docs Documents
	* @param array $rsrcs Resources
	* @param array $files Files
	* @param array $coeds Coeditors
	* @param string $categ Category
	* @param string $visib Visibility
	* @param array $rmicros Microorganisms to be removed
	* @param array $rimgs Images to be removed
	* @param array $rdocs Documents to be removed
	* @param array $rrsrcs Resources to be removed
	* @param array $rcoeds Coeditors to be removed
	* 
	* @return boolean True on success, false on failure
	*/
	public function update(
		$id, $name, $lat, $lng, $gname, $glat, $glng,
		$notes, $ref, $micros, $imgs, $docs, $rsrcs, $files, $coeds, $categ, $visib,
		$rmicros, $rimgs, $rdocs, $rrsrcs, $rcoeds
	) {
		$upd = "
			UPDATE Locations SET
				Name='{$name}', Lat='{$lat}', Lng='{$lng}',
				".(empty($gname) ? '' : "GName='{$gname}', ")."
				".(empty($glat) ? '' : "GLat='{$glat}', ")."
				".(empty($glng) ? '' : "GLng='{$glng}', ")."
				".(empty($notes) ? '' : "Notes='".mysql_real_escape_string($notes)."', ")."
				".(empty($ref) ? '' : "Ref='".mysql_real_escape_string($ref)."', ")."
				Categ='{$categ}', Visib='{$visib}',
				UpdBy='{$this->user['id']}', UpdOn='".date('Y-m-d H:i:s:ms')."', UpdNo=UpdNo+1
			WHERE ID='{$id}'
		";
		
		# Update location in database
		if($this->mysqli->query($upd)) {
			# Operate on microorganisms to be added/removed
			$micro = new Microorganism('loc', $this->mysqli, $this->user);
			$micro->operate($micros, $rmicros, $id, false);
			
			# Operate on images to be added/removed
			$img = new Image('loc', null, $this->mysqli, $this->user);
			$img->operate($imgs, $rimgs, $id);
			
			# Operate on documents to be added/removed
			$doc = new Document('loc', array('id'=>$id), $this->mysqli, $this->user);
			$doc->operate($docs, $rdocs, $id);
			
			# Operate on resources to be added/removed
			$rsrc = new Resource('loc', $this->mysqli, $this->user);
			$rsrc->operate($rsrcs, $rrsrcs, $id);
			
			# Append files
			if(!empty($files['name'])) {
				$file = new File('loc', $this->mysqli, $this->user);
				$file->append($files, $id, $categ, $visib);
			}
			
			# Operate on coeditors to be added/removed
			$coed = new Editor('loc', $this->mysqli, $this->user);
			$coed->operate($coeds, $rcoeds, $id, false);
		}
		
		# Updated location
		if(empty($this->notif)) {
			return true;
		}
		
		# Error occurred
		//echo '<pre>', var_dump($this->notif), '</pre>';
		return false;
	}
	
	/**
	* Delete location
	* Delete an existing location from the system
	* 
	* @access public
	* @param string $id Location ID
	* @param string $path Path to location
	* 
	* @return boolean True on success, false on failure
	*/
	public function delete($id) {
		$del = "UPDATE Locations SET Remove='1' WHERE ID='{$id}'";
		
		# Delete location in database
		if(!$this->mysqli->query($del)) {
			return false;
		}
	}
	
	/**
	* Recover location
	* Recover a deleted location
	* 
	* @access public
	* @param string $id Location ID
	* 
	* @return boolean true on success, false on failure
	*/
	public function recover($id) {
		# Query string to recover location
		$del = "UPDATE Locations SET Remove='0' WHERE ID='{$id}'";
		
		# Recover location in the database
		$res = $this->mysqli->query($del);
		
		# Error occurred in deletion
		if(!$res) {
			echo "ERROR: recover";
			return false;
		}
		
		# Successfully recovered location
		return true;
	} # function recover
	
	/**
	* Process appended and remove locations
	* Process on all locations associated with an area
	* which are to be appended or removed
	* 
	* @access public
	* @param array $addl Locations to be appended
	* @param array $rmvl Locations to be removed
	* @param string $id ID of area
	* @param boolean $new Locations to be appended, if non-existent, must be created
	*/
	public function operate($addl, $rmvl, $id, $sett) {
		if(!empty($addl["val"])) $this->append($addl, $id, $sett);
		if(!empty($rmvl)) $this->remove($rmvl, $id);
	}
	
	/**
	* Append locations
	* Append locations associated to that area
	* 
	* @access public
	* @param array $addl Locations to be appended
	* @param string $id ID of area
	* @param boolean $sett Settings (category, visibility)
	*/
	public function append($addl, $id, $sett) {
		# Iterate through each location
		foreach($addl['val'] as $i => $name) {
			if(empty($name)) continue;
			
			$ins = '';
			
			# Append using location ID
			if(!empty($addl['id'][$i])) {
				$ins = "INSERT INTO {$this->table} VALUES ('{$id}', '{$addl['id'][$i]}', '1', '{$this->user['id']}', '".date('Y-m-d H:i:s:ms')."')";
				
				if(!$this->mysqli->query($ins)) {
					$this->notif[] = 'ERROR: ins loc 1';
				}
			}
			else {
				# Find location
				$sel = "SELECT ID FROM Locations WHERE Name='{$name}'";
				$res = $this->mysqli->query($sel) or die();
				
				# Location is found
				if($res and !empty($res->num_rows)) {
					$loc = $res->fetch_object();
					
					$ins = "INSERT INTO {$this->table} VALUES ('{$id}', '{$loc->ID}', '1', '{$this->user['id']}', '".date('Y-m-d H:i:s:ms')."')";
					
					if(!$this->mysqli->query($ins)) {
						$this->notif[] = 'ERROR: ins loc 2';
					}
				}
				else {
					# Create new location
					$name = ($ename = empty($name)) ? null : $name;
					$lat = ($elat = !isset($addl['coord'][$i][0])) ? null : $addl['coord'][$i][0];
					$lng = ($elng = !isset($addl['coord'][$i][1])) ? null : $addl['coord'][$i][1];
					
					# Get Gmap info from the Web
					# Name is given
					if(!$ename) {
						$sel = "SELECT * FROM Locations WHERE Name='{$name}' OR GName='{$name}' LIMIT 1";
						$gcode = "http://maps.googleapis.com/maps/api/geocode/json?sensor=false&address=".urlencode($name);
					}
					# Latitude and Longitude
					else if(!($elat or $elng)) {
						$sel = "SELECT * FROM Locations WHERE (Lat='{$lat}' AND Lng='{$lng}') OR (GLat='{$lat}' AND GLng='{$lng}') LIMIT 1";
						$gcode = "http://maps.googleapis.com/maps/api/geocode/json?sensor=false&latlng={$lat},{$lng}";
					}
					# Not given
					else {
						continue;
					}
					
					# Find location
					$res = $this->mysqli->query($sel) or die();
					
					# Location found
					if(empty($res->num_rows)) {
						$gname = 'NULL';
						$glat = 'NULL';
						$glng = 'NULL';
						
						# Get location details from Gmap
						if(($ename or $elat or $elng) and ($jlocs = file_get_contents($gcode)) and !empty($jlocs)) {
							$json = json_decode($jlocs);
							
							if(!empty($json->results[0])) {
								$gname = $json->results[0]->formatted_address;
								$glat = $json->results[0]->geometry->location->lat;
								$glng = $json->results[0]->geometry->location->lng;
							}
							else {
								$glat = 0;
								$glng = 0;
							}
						}
						else {
							continue;
						}
						
						# Create new location
						$lid = $this->create(
							$name, $elat ? $glat : $lat, $elng ? $glng : $lng,
							$gname, $glat, $glng, 'NULL', null, null, null, null, $sett['categ'], $sett['visib']
						);
						
						# Created location successfully
						if($lid!==false) {
							# Append location to area
							$ins = "
								INSERT INTO {$this->table} VALUES (
									'{$id}', '{$lid}', '0', '{$this->user['id']}', '".date('Y-m-d H:i:s:ms')."'
								)
							";
							
							# Error occurred
							if(!$this->mysqli->query($ins)) {
								$this->notif[] = "ERROR: ins loc 3<br/>";
							}
						}
					}
				}
			}
		}
	}
	
	/**
	* Remove locations
	* Remove locations associated to that area
	* 
	* @access public
	* @param array $rmvl Locations to be removed
	* @param string $id ID of area
	*/
	public function remove($rmvl, $id) {
		$del = "DELETE FROM {$this->table} WHERE PID='{$id}' AND CID IN ('".implode("', '", $rmvl)."')";
		
		# Remove location assoc. with an area
		if(!$this->mysqli->query($del)) {
			$this->notif[] = "ERROR: rem micro<br/>";
		}
	}
	
	/**
	* Fetch locations
	* Fetch locations associated with an area
	* 
	* @access public
	* @param string $id ID of area
	* @param int $start Start of return results
	*/
	public function fetch($id, $start) {
		# Search all locations assoc. with that area ID
		$sel = "
			SELECT T1.* FROM Locations AS T1 INNER JOIN {$this->table} AS T2
				ON T1.ID=T2.CID AND T2.PID='{$id}' ORDER BY T2.CrtOn LIMIT {$start}, 10
		";
		
		# Find in database
		$res = $this->mysqli->query($sel);
		
		# List all locations
		if($res and !empty($res->num_rows)) { ?>
			<span class="none"> <?php
				while($loc = $res->fetch_object()) { ?>
					<li class="loc">
						<a href="main.php?loc=view&id=<?php echo $loc->ID ?>"><?php echo $loc->Name ?></a>
						<button type="button" class="remove icon read" data-area="loc" data-id="<?php echo $loc->ID ?>"></button>
					</li> <?php
				} ?>
			</span> <?php
		}
	}
	
	/**
	* Display all locations
	* Retrieve all contents of locations on a page
	* 
	* @access public
	* @param array $queries IDs of locations
	*/
	public function displayAll($queries, $opts) { ?>
		<output> <?php
			if($results = $this->search($queries, $opts, 0, 10)) {
				while($result = $results[0]->fetch_object()) {
					$this->displayContent($result, false);
				}
			} ?>
		</output> <?php
	}
	
	/**
	* Guess locations
	* Provides a list of locations (guess) on user input
	* Makes selection of location and id faster
	* 
	* @access public
	*/
	public function guess($query) {
		# Search for locations matching the query string and constrains passed
		$locs = $this->search($query, $_REQUEST, 0, 10);
		
		# Location is not found
		if(!$locs or empty($locs[1])) {
			return false;
		}
		
		while($loc = $locs[0]->fetch_object()) { ?>
			<div class="guess loc" tabindex="0" data-id="<?php echo $loc->ID ?>" data-value="<?php echo $loc->Name ?>"
				data-notes="<?php echo empty($loc->Notes) ? '' : Tool::truncate($loc->Notes, 300) ?>"
				data-lat="<?php echo $loc->Lat ?>" data-lng="<?php echo $loc->Lng ?>"
				<?php if(strlen($loc->Name) > 50) { ?> data-tool="{'head':'<?php echo $loc->Name ?>','x':'l'}" <?php } ?>>
				<a href="main.php?loc=view&id=<?php echo $loc->ID ?>"> <?php
					echo Tool::truncate($loc->Name, 50); ?></a>
			</div> <?php
		}
		
		if($_REQUEST['s']=='true') { ?>
			<div class="guess-header loc query">
				<a href="main.php?loc=view&q=<?php echo urlencode($query) ?>" target="_blank" title="<?php echo $query ?>"><?php echo Tool::truncate($query, 30) ?></a>
				<span class="right bold none" title="<?php echo ($found = $locs[0]->num_rows.' of '.$locs[1]).' items found' ?>"><?php echo $found ?></span>
			</div> <?php
		}
	}
	
	/**
	* Fetch locations
	* Fetch locations associated with an area
	* 
	* @access public
	* @param string $id ID of area
	* @param int $start Start of return results
	*/
	public function map($locs, $size) {
		# Get all location details
		while($loc = $locs->fetch_object()) {
			$json[] = array(
				"id" => $loc->ID,
				"name" => $loc->Name,
				"notes" => $loc->Notes,
				"lat" => $loc->Lat,
				"lng" => $loc->Lng,
				"link" => "main.php?loc=view&id={$loc->ID}"
			);
		}
		
		# Encode as JSON
		$json[] = array("size" => $size[0]);
		
		echo json_encode($json);
	}
	
	/**
	* Retrieve details
	* Get all details associated with location to be displayed
	* 
	* @access private
	* @param string $area Area where location is associated
	* @param string $id ID of location
	* 
	* @return mixed Returned results on search
	*/
	private function retrieve($area, $id) {
		$selSize = "SELECT FOUND_ROWS()";
		
		switch($area) {
			# Microorganism
			case 'micro':
				$sel = "
					SELECT SQL_CALC_FOUND_ROWS DISTINCT T1.* FROM Microorganisms AS T1 INNER JOIN MicroLocs AS T2
						ON T1.ID=T2.PID AND T2.CID='{$id}' AND T1.Remove='0' ORDER BY T2.CrtOn LIMIT 10
				";
			break;
			
			# Project
			case 'proj':
				$sel = "
					SELECT SQL_CALC_FOUND_ROWS DISTINCT T1.* FROM Projects AS T1 INNER JOIN ProjLocs AS T2
						ON T1.ID=T2.PID AND T2.CID='{$id}' AND T1.Remove='0' ORDER BY T2.CrtOn LIMIT 10
				";
			break;
			
			# Image
			case 'img':
				$sel = "
					SELECT SQL_CALC_FOUND_ROWS DISTINCT T1.* FROM Images AS T1 INNER JOIN LocImgs AS T2
						ON T1.ID=T2.CID AND T2.PID='{$id}' AND T1.Remove='0' ORDER BY T2.CrtOn LIMIT 10
				";
			break;
			
			# Document
			case 'doc':
				$sel = "
					SELECT SQL_CALC_FOUND_ROWS DISTINCT T1.* FROM Documents AS T1 INNER JOIN LocDocs AS T2
						ON T1.ID=T2.CID AND T2.PID='{$id}' AND T1.Remove='0' ORDER BY T2.CrtOn LIMIT 10
				";
			break;
			
			# Resource
			case 'rsrc':
				$sel = "
					SELECT SQL_CALC_FOUND_ROWS DISTINCT T1.* FROM Resources AS T1 INNER JOIN LocRsrcs AS T2
						ON T1.ID=T2.CID AND T2.PID='{$id}' AND T1.Remove='0' ORDER BY T2.CrtOn LIMIT 10
				";
			break;
		}
		
		# Find all details in database
		$res = $this->mysqli->query($sel);
		$size = $this->mysqli->query($selSize);
		$size = $size->fetch_row();
		
		# Return results and size of results
		return array($res, $size[0]);
	}
	
	/**
	* Display main location stage
	* List all locations in the main page
	* 
	* @access public
	* @param mixed $locs List of locations from returned search results
	* @param integer $size Size of rows from returned search results
	* @param string $query Query string that was searched for
	* @param array $opts Optional parameters
	* @param integer $start Starting row in mysql returned results
	*/
	public function displayMain($locs, $size, $query, $opts, $start) {
		# One location to be viewed
		$view = $locs->num_rows==1;
		# Page number
		$page = ceil(($start+1)/10);
		# Process URL params
		$optstr = Tool::optstrify($opts); ?>
		
		<div id="side">
			<div id="navis"> <?php
				# Links to previous ten items ?>
				<a href="main.php?<?php echo $optstr.(empty($query) ? '' : '&q='.$query).(empty($start) ? '&s=0' : '&s='.(intval($start)-10)) ?>"
					class="navi ui ui-button prev <?php if(empty($start)) echo 'disabled' ?>" tabindex="-1" title="Previous 10 items"></a> <?php
				# Links to next ten items ?>
				<a href="main.php?<?php echo $optstr.(empty($start) ? '&s=10' : '&s='.(intval($start)+10)) ?>"
					class="navi ui ui-button next <?php if(($locs->num_rows<10) or ($locs->num_rows*$page)>=$size) { echo 'disabled'; } ?>" tabindex="-1" title="Next 10 items"></a>
			</div> <?php
			
			# Knobs to stage location ?>
			<div id="knobs"> <?php $i = 1;
				while($loc = $locs->fetch_object()) {
					$name = Tool::truncate($trname = $loc->Name, 80); ?>
					<div id="knob<?php echo $loc->ID ?>" class="knob loc <?php if($view) echo "lock"?>" data-query="<?php echo $loc->ID ?>"
						data-id="<?php echo $loc->ID ?>" data-tool="{'head':'<b class=\'cool\'><?php echo $name ?></b>','x':'l'}">
						<?php echo $i++ ?>
					</div> <?php
				} ?>
			</div>
		</div> <?php
		
		# Labels stage items ?>
		<div id="hnotif" class="escape"> <?php
			# Shows metadata of all searched items ?>
			<span id="query" class="escape iblock" data-tool="{'head':'<?php echo ($all = (empty($query) and empty($opts['q']))) ? "All locations" : (empty($opts['q']) ? $trname : $opts['q']) ?>','x':'l'}"
				<?php if(!($nctrl = empty($_COOKIE['ctrl']['search']))) { echo 'style="width:400px"'; } ?>>
				<?php echo ($all ? "All locations" : ($view ? $name : $query)) ?>
			</span>
			
			<span>
				<span id="search-ctrls" <?php if($nctrl) { echo 'class="none"'; } ?>> <?php
					# No. of returned results
					echo '<span id="numresults">Showing '.($locs->num_rows).' of <b>'.$size.'</b> result(s)</span> on page ';
					
					# Many microorganisms are to be viewed
					$ob = isset($_REQUEST['ob']); $of = true;
					unset($opts['ob']); unset($opts['oa']);
					$optstr = Tool::optstrify($opts);
					
					# Prepare filter options and page selector ?>
					<select id="main-page" class="page navi" data-tool="{'head':'Page'}"> <?php
						for($i=0, $x=$size/10; $i<$x; $i++)	echo "<option ".((isset($opts['s']) and $opts['s']==($i*10)) ? 'selected="selected"' : '').'value="main.php?'.$optstr.(empty($query) ? '' : '&q='.$query).'&s='.($i*10).'">'.($i+1).'</option>';?>
					</select> sorted by <?php
					
					# Prepare filter options ?>
					<select class="navi" data-tool="{'head':'Sort'}">
						<option value="main.php?<?php echo $optstr ?>&ob=name&oa=asc" <?php if($ob and $_REQUEST['ob']=='title') { echo 'selected="selected"'; $of = false; } ?>>Name</option>
						<option value="main.php?<?php echo $optstr ?>&ob=notes&oa=asc" <?php if($ob and $_REQUEST['ob']=='notes') { echo 'selected="selected"'; $of = false; } ?>>Notes</option>
						<option value="main.php?<?php echo $optstr ?>&ob=crtby&oa=asc" <?php if($ob and $_REQUEST['ob']=='crtby') { echo 'selected="selected"'; $of = false; } ?>>Author</option>
						<option value="main.php?<?php echo $optstr ?>&ob=updon&oa=desc" <?php if($ob and $_REQUEST['ob']=='updon') { echo 'selected="selected"'; $of = false; } ?>>Last edited</option>
						<option value="main.php?<?php echo $optstr ?>&ob=shron&oa=desc" <?php if($ob and $_REQUEST['ob']=='shron') { echo 'selected="selected"'; $of = false; } ?>>Last shared</option>
						<option value="main.php?<?php echo $optstr ?>&ob=crton&oa=desc" <?php if($ob and $_REQUEST['ob']=='crton') { echo 'selected="selected"'; $of = false; } ?>>Date created</option>
						<option value="main.php?<?php echo $optstr ?>&ob=id&oa=asc" <?php if($ob and $_REQUEST['ob']=='id') { echo 'selected="selected"'; $of = false; } ?>>ID</option>
					</select>
				</span>
				<span <?php if(!$nctrl) { echo 'class="none"'; } ?>><?php echo "$locs->num_rows of <b>$size</b> result(s) on page <b>$page</b>";  ?></span> <button type="button" class="navi-details <?php echo (!$nctrl ? 'selected' : '') ?>" data-tool="{'head':'Search controls'}"></button>
			</span>
		</div> <?php
		
		# Contains all location headers ?>
		<div id="stage"> <?php
			# Reset pointer to first row in mysql result
			$locs->data_seek(0); ?>
			
			<span> <?php
				# List all locations on its own entry pages
				while($loc = $locs->fetch_object()) {
					# Show first the heading of each location
					$this->displayHeading($loc, $view);
				} ?>
			</span>
		</div> <?php
	}
	
	/**
	* Display a location heading
	* Displays a heading for each location in the results
	* which contains the location's title
	* 
	* @access public
	* @param mixed $loc Contains all details of the location
	* @param boolean $cont Checks if content is to be displayed too
	*/
	public function displayHeading($loc, $cont) {
		# List a location first as an area with a header that can be selected/clicked by the user in the stage
		# Data included: head (title), id (location id)
		?> <div id="area<?php echo $loc->ID ?>" class="stage area loc" data-head="<?php echo $loc->Name ?>">
			<div class="div-header loc <?php echo $cont ? "active lock" : "heading" ?>" data-id="<?php echo $loc->ID ?>" data-content="loc"
				<?php if(strlen($loc->Name)>100) echo 'data-tool="{\'head\':\''.$loc->Name.'\',\'x\':\'l\'}"' ?>>
				<a href="main.php?loc=view&id=<?php echo $loc->ID ?>" class="name" tabindex="-1">
					<?php echo Tool::truncate($loc->Name, 100) ?></a>
			</div> <?php
			
			# Show location's contents if necessary
			if($cont) {
				$this->displayContent($loc, $cont);
			} ?>
		</div> <?php
	}
	
	/**
	* Display contents of location
	* Displays the contents of a location, from its title
	* to its associated items in other areas of the system
	* 
	* @access public
	* @param mixed $loc Contains all details of the location
	* @param boolean $cont Checks if only one location is found in results
	*/
	public function displayContent($loc, $cont) {
		?> <div class="div-content">
			<form id="form-loc<?php echo $loc->ID ?>" class="loc" name="form-loc" method="post" action="process.php?loc=edit" enctype="multipart/form-data" novalidate="novalidate">
			<div class="div-upper">
				<div class="div-body">
					<div class="div-peel name"><b>Name</b></span></div>
					<div class="div-case">
						<textarea name="name" class="title reqd read" readonly="readonly" rows="<?php echo ceil(strlen($loc->Name)/100) ?>"><?php echo $loc->Name ?></textarea>
					</div>
					
					<div class="div-peel peel off next coord open"><b>Coordinates</b></div>
					<div class="div-case">
						<label>Latitude:</label> <input name="lat" type="text" class="reqd abled coord read" readonly="readonly" value="<?php echo $loc->Lat ?>" style="width:180px"/> &nbsp; &nbsp; &nbsp; &nbsp;
						<label>Longitude:</label> <input name="lng" type="text" class="reqd abled coord read" readonly="readonly" value="<?php echo $loc->Lng ?>" style="width:180px"/>
					</div>
					
					<div class="div-peel peel on next open loc"><b><span>Google Maps</span></b></span></div>
					<div class="div-case none">
						<label>Name:</label> <input name="gname" class="loc gmap read" readonly="readonly" type="text" value="<?php echo $loc->GName ?>" data-guess="loc=guess"/><hr/>
						<label>Latitude:</label> <input name="glat" type="text" class="abled coord read" readonly="readonly" value="<?php echo $loc->GLat ?>" style="width:180px"/> &nbsp; &nbsp; &nbsp; &nbsp;
						<label>Longitude:</label> <input name="glng" type="text" class="abled coord read" readonly="readonly" value="<?php echo $loc->GLng ?>" style="width:180px"/>
					</div>
					
					<div class="div-peel peel <?php echo ($flag = (empty($loc->Notes) or $loc->Notes=='NULL')) ? "on" : "off open" ?> next notes"><b>Notes</b></div>
					<div class="div-case <?php if($flag) echo "none" ?>">
						<textarea name="notes" class="read abled" readonly="readonly" rows="<?php echo empty($loc->Notes) ? '5' : ceil(strlen($loc->Notes)/100) ?>"><?php echo $loc->Notes ?></textarea>
					</div> <?php
					
					//MICROORGANISMS///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
					
					list($resMicro, $sizeMicro) = $this->retrieve('micro', $loc->ID); ?>
					
					<div class="div-peel peel <?php echo ($empty = empty($sizeMicro)) ? "on" : "off open" ?> next micro">
						<b>Microorganisms</b> <span><?php echo $sizeMicro ?></span>
					</div>
					<div class="div-case <?php if($empty) echo "none" ?>">
						<ol> <?php
							if(!$empty) {
								while($micro = $resMicro->fetch_object()) { ?>
									<li>
										<a href="main.php?micro=view&id=<?php echo $micro->ID ?>" class="micro"><i><?php
											echo $micro->Name ?></i></a>
										<button type="button" class="remove icon read" data-area="micro" data-id="<?php echo $micro->ID ?>"></button>
									</li> <?php
								}
							} ?>
						</ol>
						
						<div class="none">
							<div class="default">
								<input type="text" class="micro" name="micro[val][]" placeholder="Scientific name" data-guess="micro=guess"/>
								<button class="append icon" type="button" data-id="0"></button>
								<input type="hidden" name="micro[id][]" class="abled"/>
							</div>
							<div class="micros"></div>
						</div>
						<button type="button" class="addmore peel on prev read" data-on="Add" data-off="Cancel">Add</button>
					</div> <?php
					
					//PROJECTS////////////////////////////////////////////////////////////////////////////////////////////////////////////
					
					list($resProj, $sizeProj) = $this->retrieve('proj', $loc->ID); ?>
					
					<div class="div-peel peel <?php echo ($empty = empty($sizeProj)) ? "on" : "off open" ?> next proj" name="proj">
						<b>Projects</b> <span><?php echo $sizeProj ?></span>
					</div>
					<div class="div-case <?php if($empty) echo "none" ?>">
						<ol> <?php
							if(!$empty) {
								while($proj = $resProj->fetch_object()) { ?>
									<li>
										<a href="main.php?proj=view&id=<?php echo $proj->ID ?>"><?php echo $proj->Title ?></a>
										<input type="hidden" name="proj[id][]" class="abled" value="<?php echo $proj->ID ?>"/>
									</li> <?php
								}
							} ?>
						<ol>
					</div> <?php 
					
					//IMAGES//////////////////////////////////////////////////////////////////////////////////////////////////////////////
					
					list($resImg, $sizeImg) = $this->retrieve('img', $loc->ID); ?>
					
					<div class="div-peel peel <?php echo ($empty = empty($sizeImg)) ? "on" : "off open" ?> next img">
						<b>Images</b> <span><?php echo $sizeImg ?></span>
					</div>
					<div class="div-case <?php if($empty) echo "none" ?>"> <?php
						if(!$empty) {
							$img = $resImg->fetch_object();
							$imgPath = $img->Path;
							$resImg->data_seek(0);
							
							while($img = $resImg->fetch_object()) { ?>
								<span class="img">
									<a href="main.php?img=view&id=<?php echo $img->ID ?>">
										<img class="stage file locked ghost" src="<?php echo $img->Thumb ?>" alt="<?php echo $img->Name ?>" style="width:<?php echo (125/$img->Height)*$img->Width ?>px"
											data-id="<?php echo $img->ID ?>" data-src="<?php echo $img->Path ?>" data-visib="<?php echo $img->Visib ?>" data-categ="<?php echo $img->Categ ?>"
											data-tool="{'head':'<span class=\'permalink\'><a href=\'main.php?img=view&id=<?php echo $img->ID ?>\' target=\'_blank\'><?php echo $img->Title ?></a></span>','stay':'true','x':'l'}"/></a>
									<div class="ctrl-img img none">Remove</div> <input name="rimg[]" type="checkbox" class="abled none" value="<?php echo $img->ID ?>"/>
								</span> <?php
							} ?>
							
							<a class="fetch img tick" data-area="loc" data-id="<?php echo $loc->ID ?>" data-start="10">Show more</a> <?php
						} ?>
						
						<div class="none">
							<div class="default">
								<input name="img[val][]" class="img" type="text" placeholder="Image title" data-guess="img=guess"/>
								<button class="append icon" type="button" data-area="img" data-id="0"></button>
								<input name="img[id][]" type="hidden" class="abled"/>
							</div>
							<div class="imgs"></div>
						</div>
						
						<button type="button" class="addmore peel on prev read" data-on="Add" data-off="Cancel">Add</button>
					</div> <?php 
					
					//DOCUMENTS//////////////////////////////////////////////////////////////////////////////////////////////////////////////
					
					list($resDoc, $sizeDoc) = $this->retrieve('doc', $loc->ID); ?>
					
					<div class="div-peel peel <?php echo ($empty = empty($sizeDoc)) ? "on" : "off open" ?> next doc">
						<b>Documents</b> <span><?php echo $sizeDoc ?></span>
					</div>
					<div class="div-case <?php if($empty) echo "none" ?>"> <?php
						if(!$empty) { ?>
							<ol> <?php
								while($doc = $resDoc->fetch_object()) { ?>
									<li>
										<a href="main.php?doc=view&id=<?php echo $doc->ID ?>" data-tool="{'head':'<?php echo $doc->Title ?>','x':'l'}"><?php echo Tool::truncate($doc->Title, 80) ?></a>
										<button class="small" data-title="<?php echo $doc->Title ?>" data-doc="<?php echo $doc->Path ?>">Open</button>
										<button type="button" class="remove icon read" data-area="doc" data-id="<?php echo $doc->ID ?>"></button>
									</li> <?php
								} ?>
							</ol>
							<a class="fetch doc tick" data-area="loc" data-id="<?php echo $loc->ID ?>" data-start="10">Show more</a> <?php
						} ?>
						
						<div class="none">
							<div class="default">
								<input type="text" class="doc" name="doc[val][]" placeholder="Document title" data-guess="doc=guess"/>
								<button class="append icon" type="button" data-area="doc" data-id="0"></button>
								<input type="hidden" name="doc[id][]" class="abled"/>
							</div>
							<div class="docs"></div>
						</div>
						
						<button type="button" class="addmore peel on prev read" data-on="Add" data-off="Cancel">Add</button>
					</div> <?php
					
					//RESOURCES////////////////////////////////////////////////////////////////////////////////////////////////////////////
					
					list($resRsrc, $sizeRsrc) = $this->retrieve('rsrc', $loc->ID); ?>
					
					<div class="div-peel peel <?php echo ($empty = empty($sizeRsrc)) ? "on" : "off open" ?> next rsrc">
						<b>Resources</b> <span><?php echo $sizeRsrc ?></span>
					</div>
					<div class="div-case <?php if($empty) echo "none" ?>"> <?php
						if(!$empty) { ?>
							<ol> <?php
								while($rsrc = $resRsrc->fetch_object()) { ?>
									<li class="rsrc">
										<a href="main.php?rsrc=view&id=<?php echo $rsrc->ID ?>"><?php echo $rsrc->Title ?></a>
										<button type="button" class="remove icon read" data-area="rsrc" data-id="<?php echo $rsrc->ID ?>"></button>
									</li> <?php
								} ?>
							</ol>
							<a class="fetch rsrc tick" data-area="loc" data-id="<?php echo $loc->ID ?>" data-start="10">Show more</a> <?php
						} ?>
						
						<div class="none">
							<div class="default">
								<input type="text" class="rsrc" name="rsrc[val][]" placeholder="Resource title" data-guess="rsrc=guess"/>
								<button class="append icon" type="button" data-area="rsrc" data-id="0"></button>
								<input type="hidden" name="rsrc[id][]" class="abled"/>
							</div>
							<div class="rsrcs"></div>
						</div>
						
						<button type="button" class="addmore peel on prev read" data-on="Add" data-off="Cancel">Add</button>
					</div>
					
					<div class="div-peel peel <?php echo ($empty = (empty($loc->Ref) or $loc->Ref=='NULL')) ? "on" : "off open" ?> next ref">
						<b>References</b></div>
					<div class="div-case <?php if($empty) echo "none" ?>">
						<textarea name="ref" rows="<?php echo $empty ? '3' : ceil(strlen($loc->Ref)/100) ?>" class="read abled" readonly="readonly"> <?php
							echo $loc->Ref ?></textarea>
					</div> <?php
					
					//FILES////////////////////////////////////////////////////////////////////////////////////////////////////////////*/ ?>
					
					<div class="div-peel peel on next file none"><b>Files</b></div>
					<div class="div-case none file">
						<input name="file[]" type="file" multiple="multiple" accept="image/jpeg,image/gif,application/pdf"/>
					</div> <?php
					
					//SETTINGS////////////////////////////////////////////////////////////////////////////////////////////////////////////*/ ?>
					
					<div class="div-peel peel on next safe none"><b>Settings</b><span class="setting help"></span></div>
					<div class="div-case none safe"></div>
				</div>
				
				<div class="div-head">
					<a class="open loc" data-lat="<?php echo $loc->Lat ?>" data-lng="<?php echo $loc->Lng ?>"
						data-name="<?php echo empty($loc->GName) ? $loc->Name : $loc->GName ?>" data-notes="<?php echo $loc->Notes ?>" data-id="<?php echo $loc->ID ?>">
						<img src="http://maps.googleapis.com/maps/api/staticmap?center=<?php echo $loc->Lat.",".$loc->Lng ?>&zoom=8&size=200x200&sensor=false"
							class="loc ghost" style="width:200px;height:200px" alt="<?php echo $loc->Name ?>"/></a>
					
					<div class="controls">
						<a href="http://maps.google.com/?ll=<?php echo $loc->Lat.','.$loc->Lng ?>&z=10" target="_blank">
							<span class="open dial button" title="Google Maps" type="button">Open</span></a><hr/>
						<button class="share dial" data-area="loc" data-id="<?php echo $loc->ID ?>" type="button"><span>Share</span></button><hr/>
						
						<button class="details dial" type="button" data-area="loc" data-id="<?php echo $loc->ID ?>" data-name="<?php echo $loc->Name ?>"><span>Details</span></button>
						
						<button class="stat dial peel on next" type="button"><b>Contents</b></button>
						<ul class="metas none">
							<li class="meta">Microorganisms <span><?php echo $sizeMicro ?></span></li>
							<li class="meta">Projects <span><?php echo $sizeProj ?></span></li>
							<li class="meta">Images <span><?php echo $sizeImg ?></span></li>
							<li class="meta">Documents <span><?php echo $sizeDoc ?></span></li>
							<li class="meta">Resources <span><?php echo $sizeRsrc ?></span></li>
						</ul> <?php
						
						$sett = new Setting('loc', null, $this->mysqli, $this->user);
						$verified = $sett->verify($loc->ID);
						
						if($verified) { ?><hr/>
							<button class="edit dial" data-area="loc" data-id="<?php echo $loc->ID ?>" type="reset"><span>Edit</span></button> <?php
						} ?>
					</div>
				</div>
				
				<div class="div-mind">
					<input name="id" type="text" class="id abled" value="<?php echo $loc->ID ?>"/>
					<input name="upd" type="checkbox" class="abled none" value="<?php echo $loc->ID ?>"/>
					<input name="recov" type="checkbox" class="recov abled" value="<?php echo $loc->ID ?>"/>
					<input name="del" type="checkbox" class="del abled none" value="<?php echo $loc->ID ?>"/>
				</div>
			</div>
			
			<div class="div-dial"> <?php
				if($loc->Remove=='0') { ?>
					<button class="delete tick read left" type="button" form="form-loc<?php echo $loc->ID ?>" data-area="loc">Delete</button> <?php
				}
				else { ?>
					<button class="recover tick read left" type="button" form="form-loc<?php echo $loc->ID ?>" data-area="loc">Recover</button> <?php
				} ?>
				<button type="button" form="form-loc<?php echo $loc->ID ?>" class="cancel edit read">Cancel</button>
				<button type="submit" class="read">Update</button> <?php
				
				if(!$cont) { ?>
					<button type="button" class="close-content reset">Close</button> <?php
				} ?>
			</div>
			</form>
		</div> <?php
	}
} ?>